home *** CD-ROM | disk | FTP | other *** search
/ HPAVC / HPAVC CD-ROM.iso / PRUS101.ZIP / FDIRBOX.PAS < prev    next >
Pascal/Delphi Source File  |  1994-12-19  |  27KB  |  1,034 lines

  1. UNIT FDIRBOX;
  2.  (***************************************************************************
  3.  
  4.          RELEASE 1.07 - as contained in the file PRUS101.LZH
  5.                  by Paul Schubert, 2:244/1181.18,  GERMANY
  6.  
  7.                --------------------------------------------
  8.                 organized for Fido's PASCAL related echoes
  9.                --------------------------------------------
  10.  
  11.     06/21/1994 to --/--/---- by Paul Schubert, 2:244/1181.18,  GERMANY
  12.  
  13.  
  14.            As far as third party copyrights are not violated this
  15.            source code is hereby placed to the public domain. Use
  16.            it whatever way you want, but use AT YOUR OWN RISK.
  17.  
  18.            In case you should modify the source rather send your
  19.            modifications to the unit's current organizer (see above for
  20.            NM address) than to spread it on your own. This will help to
  21.            keep the unit updated and grant a certain standard to all
  22.            other users as well.
  23.  
  24.            The unit is currently still under work. So it might greatly
  25.            benefit of your participation.
  26.  
  27.            Those who contributed to the following piece of source,
  28.            listed in alphabethical order:
  29.         ================================================================
  30.            Orazio Czerwenka, Paul Schubert ...
  31.         ================================================================
  32.            YOUR NAME WILL APPEAR HERE IF YOU CONTRIBUTE USEFUL SOURCE.
  33.  
  34.            Credits in your own programs are owed to Paul Schubert who
  35.            made his former stand alone unit DIRBOX a substantial part
  36.            of the PRUSSG project.
  37.  
  38.  ***************************************************************************)
  39.  
  40. {$I FDEFINE.DEF} { Use the general include file for conditional defines and
  41.                common compiler directives ... }
  42.  
  43. {$F+,R-,S-}  { ... and afterwards add the unit's specific defines }
  44.  
  45. INTERFACE
  46.  
  47.  
  48. {.$DEFINE USEMOUSE}
  49. {$DEFINE SPDISP} { 2 VERSCHIEDENE DISPLAY METHODEN SIND WÄHLBAR }
  50.  
  51.  
  52. USES  FCRT         { for HIDECURSOR, NORMCURSOR and PUTCHARATR }
  53.       ,FDOS
  54. {$IFDEF USEMOUSE}
  55.       ,MAUSI,KBD
  56. {$ENDIF USEMOUSE}
  57.       ,DOS
  58.       ;
  59.  
  60.  
  61. CONST ANZINCLUDE = 5;
  62.  
  63.       TANONSEL        : BYTE = $0F; { TEXTATTRIB non selected }
  64.       TASELECT        : BYTE = $70; { TEXTATTRIB selected }
  65.       TARAND          : BYTE = $1E; { border }
  66.       TATITEL         : BYTE = $5E; { title }
  67.       TATAGED         : BYTE = $0C; { tagged }
  68.       TATAGEDS        : BYTE = $74; { tagged and selected }
  69.  
  70.       EXCLUDE         : ARRAY[1..ANZINCLUDE] OF STRING[12] = ('','','','','');
  71.       INCLUDE         : ARRAY[1..ANZINCLUDE] OF STRING[12] = ('','','','','');
  72.       SEARCHFOR       : STRING[12] = ' ';
  73.  
  74.       DIRMARK         : CHAR = #254;
  75.       DRIVEMARK       : CHAR = #4;
  76.       DIRDISPLAYMODE  : BYTE = 1;
  77.       DRIVESALLOWED   : BOOLEAN = TRUE;
  78.       DIRSALLOWED     : BOOLEAN = TRUE;
  79.  
  80.       EXITKEYS        : ARRAY[1..8] OF WORD = (0,0,0,0,0,0,0,0);
  81.       EXITKEY         : BYTE = 0;
  82.  
  83. VAR   PRINTNAME       : PROCEDURE(S:STRING);
  84.  
  85.  
  86. FUNCTION  SELECTFILE(PTH,NAME:STRING):STRING;
  87.  
  88.  
  89. IMPLEMENTATION
  90.  
  91.  
  92. CONST WWIDMAX    = 4;
  93.       WHIGMAX    = 23;
  94.       WWID       : BYTE = 3;   { window width }
  95.       WHIG       : BYTE = 8;   { window height }
  96.       ANZWID     : BYTE = 14;
  97.  
  98.  
  99. TYPE  STR6       = STRING[6];
  100.       STR12      = STRING[12];
  101.       STR80      = STRING[80];
  102.       DIRPTR     = ^DIRREC;
  103.       DIRREC     = RECORD
  104.         NAME       : STR12;
  105.         ATTR       : BYTE;
  106.         TIME,SIZE  : LONGINT;
  107.         NEXT       : DIRPTR;
  108.         TAG        : BOOLEAN;
  109.       END;
  110.  
  111.  
  112. VAR   SCR              : POINTER;
  113.       WOM,WUM          : WORD;
  114.       TAALT,XPOS,YPOS  : BYTE;
  115.       AKTPATH          : STR80;
  116.       AllDrives        : String[26];
  117.  
  118. { ------------------------------- }
  119.  
  120. CONST EXTENDEDKEYS : BOOLEAN = FALSE;
  121.  
  122.  
  123. FUNCTION READKEYWORD:WORD;
  124. VAR   R  : REGISTERS;
  125. BEGIN
  126.   IF EXTENDEDKEYS THEN R.AH := $10 ELSE R.AH := 0;
  127.   INTR($16,R);
  128.   IF NOT EXTENDEDKEYS AND (R.AL = $E0) THEN R.AL := 0;
  129.   READKEYWORD := R.AX;
  130. END; { READKEYWORD }
  131.  
  132. PROCEDURE STUFFKEY(W:WORD); { put WORD into KEYBOARD BUFFER }
  133. VAR   R    : REGISTERS;
  134. BEGIN
  135.   R.AH := 5;
  136.   R.CX := W;
  137.   INTR($16,R);
  138. END; { STUFFKEY }
  139.  
  140. { ------------------------------- }
  141.  
  142. FUNCTION  ATTRTOSTR(ATTR:BYTE):STR6;
  143. VAR   ST  : STR6;
  144. BEGIN { ATTRTOSTR }
  145.   IF (ATTR AND READONLY ) = 0 THEN ST := '-' ELSE ST := 'R';
  146.   IF (ATTR AND HIDDEN   ) = 0 THEN ST := ST + '-' ELSE ST := ST + 'H';
  147.   IF (ATTR AND ARCHIVE  ) = 0 THEN ST := ST + '-' ELSE ST := ST + 'A';
  148.   IF (ATTR AND SYSFILE  ) = 0 THEN ST := ST + '-' ELSE ST := ST + 'S';
  149.   IF (ATTR AND DIRECTORY) = 0 THEN ST := ST + '-' ELSE ST := ST + 'D';
  150.   IF (ATTR AND VOLUMEID ) = 0 THEN ST := ST + '-' ELSE ST := ST + 'V';
  151.   ATTRTOSTR := ST;
  152. END; { ATTRTOSTR }
  153.  
  154.  
  155. FUNCTION EXPAND(NAME : STR12):STR12;
  156. VAR   A,B  : BYTE;
  157.       S    : STR12;
  158. BEGIN { EXPAND }
  159.   A := POS('.',NAME);
  160.   IF A > 1 THEN BEGIN
  161.     S := '';
  162.     FOR B := A TO 8 DO S := S + ' ';
  163.     INSERT(S,NAME,A);
  164.   END;
  165.   EXPAND := NAME;
  166. END; { EXPAND }
  167.  
  168.  
  169. PROCEDURE READDIR(PATH:STRING;VAR FILES:WORD;VAR DIRS:WORD;VAR START:DIRPTR);
  170. VAR   EINTRAG  : SEARCHREC;
  171.       NEU      : DIRPTR;
  172.       I        : WORD;
  173.       DN       : DIRSTR;
  174.       FN       : NAMESTR;
  175.       FE       : EXTSTR;
  176.  
  177. PROCEDURE INSERTLIST(VAR ALT,NEU:DIRPTR);
  178. VAR   P  : POINTER;
  179. BEGIN
  180.   IF ALT = NIL THEN BEGIN
  181. { sort to end of list }
  182.     ALT := NEU;
  183.   END ELSE BEGIN
  184.     IF ALT^.NAME > NEU^.NAME { name ascending }
  185.     THEN BEGIN
  186. { hook an entry into the list }
  187.       P := ALT;
  188.       ALT := NEU;
  189.       NEU^.NEXT := P;
  190.     END ELSE
  191. { repeat searching }
  192.       IF ALT^.NEXT = NIL THEN BEGIN
  193. { end of list }
  194.         ALT^.NEXT := NEU;
  195.       END ELSE BEGIN
  196. { go on recursively }
  197.         INSERTLIST(ALT^.NEXT,NEU);
  198.       END;
  199.   END;
  200. END; { INSERTLIST }
  201.  
  202. FUNCTION TEST(VAR EINTRAG:SEARCHREC):BOOLEAN;
  203. VAR   I  : BYTE;
  204.  
  205. FUNCTION WILL:BOOLEAN;
  206. VAR   I  : BYTE;
  207. BEGIN
  208.   WILL := TRUE;
  209.   IF INCLUDE[1] = '' THEN EXIT;
  210.   WILL := FALSE;
  211.   FOR I := 1 TO ANZINCLUDE DO BEGIN
  212.     IF (INCLUDE[I] <> '') AND
  213.        (POS(INCLUDE[I],EINTRAG.NAME) <> 0) THEN WILL := TRUE;
  214.   END; { NEXT I }
  215. END; { WILL }
  216.  
  217. BEGIN { TEST }
  218.   TEST := FALSE;
  219.   WITH EINTRAG DO BEGIN
  220.     IF NOT WILL THEN EXIT;
  221.  
  222.     FOR I := 1 TO ANZINCLUDE DO BEGIN
  223.       IF (EXCLUDE[I] <> '') AND
  224.          (POS(EXCLUDE[I],NAME) <> 0) THEN EXIT;
  225.     END; { NEXT I }
  226.     TEST := (ATTR AND VOLUMEID) = 0;
  227.   END; { WITH EINTRAG }
  228. END; { TEST }
  229.  
  230. PROCEDURE SPEICHERN;
  231. BEGIN
  232.   IF (EINTRAG.ATTR = DIRECTORY) AND (EINTRAG.NAME[1] <> DRIVEMARK) THEN BEGIN
  233.     IF LENGTH(EINTRAG.NAME) = 12 THEN DELETE(EINTRAG.NAME,9,1);
  234.     IF EINTRAG.NAME = '..' THEN INSERT(' ',EINTRAG.NAME,1)
  235.                            ELSE INSERT(DIRMARK,EINTRAG.NAME,1);
  236.   END;
  237.   IF MAXAVAIL < 50 THEN EXIT; {@@@ keep wolves away }
  238.   NEW(NEU);
  239.   WITH NEU^ DO BEGIN
  240.     NAME := EINTRAG.NAME;
  241.     ATTR := EINTRAG.ATTR;
  242.     TIME := EINTRAG.TIME;
  243.     SIZE := EINTRAG.SIZE;
  244.     TAG  := FALSE;
  245.     NEXT := NIL;
  246.   END; { WITH }
  247.  
  248.   INSERTLIST(START,NEU);
  249. END; { SPEICHERN }
  250.  
  251. BEGIN { READDIR }
  252.   FILES := 0;
  253.   DIRS  := 0;
  254.   I := LENGTH(PATH);
  255.   WHILE (I > 1) AND (PATH[I] <> '\') DO DEC(I);
  256.  
  257.   IF DRIVESALLOWED AND (I <= 3) THEN BEGIN
  258.     EINTRAG.NAME := DRIVEMARK+'A:';
  259.     FOR I := 1 TO LENGTH(AllDrives) DO BEGIN
  260.       IF GETDRIVETYPE(Ord (AllDrives[I]) - Ord('A') + 1) <> dtError THEN BEGIN
  261.         EINTRAG.NAME[2] := CHR(I+$40);
  262.         EINTRAG.ATTR    := DIRECTORY;
  263.         EINTRAG.SIZE    := -1; { a drive : no size }
  264.         EINTRAG.TIME    := -1; { a drive : no date }
  265.         INC(DIRS);
  266.         SPEICHERN;
  267.       END;
  268.     END; { NEXT I }
  269.   END;
  270.  
  271.   IF DIRSALLOWED THEN BEGIN
  272.     FSPLIT(PATH,DN,FN,FE);
  273.     FINDFIRST(DN+'*.*',DIRECTORY,EINTRAG);
  274.     WHILE DOSERROR = 0 DO BEGIN
  275.       IF ((EINTRAG.ATTR AND DIRECTORY) > 0) AND
  276.          (EINTRAG.NAME <> '.') THEN BEGIN
  277.            INC(DIRS);
  278.            EINTRAG.SIZE := -1; { don't show size for directories }
  279.            SPEICHERN;
  280.          END;
  281.       FINDNEXT(EINTRAG);
  282.     END; { WHILE }
  283.   END;
  284.  
  285.   FINDFIRST(PATH,ANYFILE AND NOT DIRECTORY,EINTRAG);
  286.   WHILE DOSERROR = 0 DO BEGIN
  287.     IF TEST(EINTRAG) THEN BEGIN
  288.       INC(FILES);
  289.       SPEICHERN;
  290.     END;
  291.     FINDNEXT(EINTRAG);
  292.   END; { WHILE }
  293. END; { READDIR }
  294.  
  295.  
  296. PROCEDURE FREEDIR(VAR DP:DIRPTR);
  297. BEGIN { FREEDIR }
  298.   IF DP <> NIL THEN BEGIN
  299.     FREEDIR(DP^.NEXT);
  300.     DISPOSE(DP);
  301.     DP := NIL;
  302.   END;
  303. END; { FREEDIR }
  304.  
  305.  
  306. {3.12.94}
  307. PROCEDURE GETANZWID;
  308. BEGIN
  309.   CASE DIRDISPLAYMODE OF
  310.     2 : ANZWID := 23; { name, size }
  311.     3 : ANZWID := 38; { name, size, date }
  312.     4 : ANZWID := 45; { name, size, attributes, date }
  313.   ELSE
  314.     ANZWID := 14; { name only }
  315.   END; { CASE DIRDISPLAYMODE }
  316. END; { GETANZWID }
  317.  
  318.  
  319. FUNCTION  SELECTDIRREC(START:DIRPTR;MAXANZ:WORD):DIRPTR;
  320. TYPE  S2  = STRING[2];
  321. VAR   SPALTE             : BYTE;
  322.       I,PO,ZEILE,MAXAUS,
  323.       AUSSCHN,NTAGS      : WORD;
  324.       ANZAHL             : INTEGER;
  325.       DX,DY,DXA,DYA      : INTEGER;
  326.       ENDE               : BOOLEAN;
  327.       CH2,CH1            : CHAR;
  328.       MKB                : WORD ABSOLUTE CH1;
  329.       ST,SR              : STRING[14];
  330.       P                  : DIRPTR;
  331.       POINTERLIST        : ARRAY[0..WWIDMAX,1..WHIGMAX] OF DIRPTR;
  332. LABEL CALCULATE_WINDOW;
  333.  
  334. FUNCTION ZS2(NR:INTEGER):S2;
  335. VAR   S  : S2;
  336. BEGIN
  337.   STR(NR:2,S);
  338.   IF S[1] = ' ' THEN S[1] := '0';
  339.   ZS2 := S;
  340. END; { ZS2 }
  341.  
  342. PROCEDURE ZEIGNAME(P:DIRPTR);
  343. VAR   DT   : DATETIME;
  344.       TAM  : BYTE;
  345. BEGIN
  346.   TAM := TEXTATTR;
  347.   IF P^.TAG THEN BEGIN
  348.     IF TEXTATTR = TASELECT THEN TEXTATTR := TATAGEDS
  349.                            ELSE TEXTATTR := TATAGED
  350.   END;
  351.   WITH P^ DO BEGIN
  352. {@@@}
  353.     IF (ATTR AND DIRECTORY) = DIRECTORY
  354.       THEN ST := ' '+NAME+'\'
  355.       ELSE ST := ' '+EXPAND(NAME);
  356.     WRITE(ST,'':14-LENGTH(ST));
  357.     IF DIRDISPLAYMODE >= 2 THEN BEGIN
  358.       IF SIZE <> -1 THEN WRITE(SIZE:8)
  359.                     ELSE WRITE('        ');
  360.     END;
  361.     IF (DIRDISPLAYMODE = 4) AND (P^.NAME[1] <> DRIVEMARK) THEN BEGIN
  362.       WRITE(' '+ATTRTOSTR(ATTR));
  363.     END;
  364.     IF DIRDISPLAYMODE >= 3 THEN BEGIN
  365.       IF (TIME <> 0) AND (TIME <> -1) THEN BEGIN
  366.         UNPACKTIME(TIME,DT);
  367.         WITH DT DO
  368.           WRITE(' ',DAY:2,'.'+ZS2(MONTH)+'.'+ZS2(YEAR MOD 100)+
  369.                  ' '+ZS2(HOUR)+':'+ZS2(MIN));
  370.       END;
  371.     END;
  372.     IF DIRDISPLAYMODE <> 1 THEN WRITE(' ');
  373.   END; { WITH P^ }
  374.   TEXTATTR := TAM;
  375. END; { ZEIGNAME }
  376.  
  377. PROCEDURE BILDAUFBAU;
  378. VAR   S,Z  : WORD;
  379. {$IFDEF SPDISP}
  380.       I    : WORD;
  381. {$ENDIF SPDISP}
  382. BEGIN
  383.   FILLCHAR(POINTERLIST,SIZEOF(POINTERLIST),0);
  384.   P := START;
  385.   FOR S := 1 TO AUSSCHN * SUCC(WWID) DO P := P^.NEXT;
  386.  
  387.   TEXTATTR := TANONSEL;
  388.   S := 0; Z := 1;
  389.  
  390. {$IFDEF SPDISP}
  391. (*
  392.   CLRSCR;
  393. *)
  394.   FOR I := 1 TO AUSSCHN * WHIG DO P := P^.NEXT;
  395. (*
  396.   WHILE ( (P <> NIL) AND (S <= WWID) ) DO BEGIN
  397. *)
  398.   WHILE S <= WWID DO BEGIN
  399.     GOTOXY(2+S*ANZWID,Z);
  400.     IF P <> NIL THEN BEGIN
  401.       POINTERLIST[S,Z] := P;
  402.       ZEIGNAME(P);
  403.       P := P^.NEXT;
  404.     END ELSE CLREOL;
  405.     INC(Z);
  406.     IF Z > WHIG THEN BEGIN
  407.       Z := 1;
  408.       INC(S);
  409.     END;
  410.   END; { WHILE }
  411. {$ELSE}
  412.   WHILE ( (P <> NIL) AND (Z <= WHIG) ) DO BEGIN
  413.     GOTOXY(2+S*ANZWID,Z);
  414.     POINTERLIST[S,Z] := P;
  415.     ZEIGNAME(P);
  416.  
  417.     P := P^.NEXT;
  418.     INC(S);
  419.     IF S > WWID THEN BEGIN
  420.       S := 0;
  421.       INC(Z);
  422.       CLREOL;
  423.     END;
  424.   END; { WHILE }
  425.   CLREOS;
  426. {$ENDIF ELSEIF SPDISP}
  427. END; { BILDAUFBAU }
  428.  
  429. PROCEDURE RECHTS; FORWARD;
  430. PROCEDURE LINKS; FORWARD;
  431.  
  432. PROCEDURE AUFWAERTS;
  433. BEGIN
  434.   IF ZEILE > 1 THEN DEC(ZEILE)
  435.   ELSE BEGIN
  436. {$IFDEF SPDISP}
  437.     IF (SPALTE+AUSSCHN) > 0 THEN BEGIN
  438.       ZEILE := WHIG;
  439.       LINKS;
  440.       WHILE POINTERLIST[SPALTE,ZEILE] = NIL DO DEC(ZEILE);
  441.     END;
  442. {$ELSE}
  443.     IF AUSSCHN > 0 THEN BEGIN
  444.       DEC(AUSSCHN);
  445.       BILDAUFBAU;
  446.     END;
  447. {$ENDIF ELSEIF SPDISP}
  448.   END;
  449. END; { AUFWAERTS }
  450.  
  451. PROCEDURE ABWAERTS;
  452. BEGIN
  453.   IF ZEILE < WHIG THEN BEGIN
  454.     IF (POINTERLIST[SPALTE,SUCC(ZEILE)] <> NIL) THEN INC(ZEILE);
  455.   END ELSE BEGIN
  456. {$IFDEF SPDISP}
  457.     ZEILE := 1;
  458.     RECHTS;
  459. {$ELSE}
  460.     IF AUSSCHN < MAXAUS THEN BEGIN
  461.       INC(AUSSCHN);
  462.       BILDAUFBAU;
  463.     END;
  464.     WHILE POINTERLIST[SPALTE,ZEILE] = NIL DO DEC(SPALTE);
  465. {$ENDIF ELSEIF SPDISP}
  466.   END;
  467. END; { ABWAERTS }
  468.  
  469. PROCEDURE RECHTS;
  470. BEGIN
  471.   IF SPALTE < WWID THEN BEGIN
  472.     IF POINTERLIST[SUCC(SPALTE),ZEILE] <> NIL THEN INC(SPALTE);
  473.   END ELSE BEGIN
  474. {$IFDEF SPDISP}
  475.     IF AUSSCHN < MAXAUS THEN BEGIN
  476.       INC(AUSSCHN);
  477.       BILDAUFBAU;
  478.     END;
  479.     WHILE POINTERLIST[SPALTE,ZEILE] = NIL DO DEC(ZEILE);
  480. {$ELSE}
  481.     SPALTE := 0;
  482.     ABWAERTS;
  483. {$ENDIF ELSEIF SPDISP}
  484.   END;
  485. END; { RECHTS }
  486.  
  487. PROCEDURE LINKS;
  488. BEGIN
  489.   IF SPALTE > 0 THEN DEC(SPALTE) ELSE BEGIN
  490. {$IFDEF SPDISP}
  491.     IF AUSSCHN > 0 THEN BEGIN
  492.       DEC(AUSSCHN);
  493.       BILDAUFBAU;
  494.     END;
  495. {$ELSE}
  496.     IF (ZEILE + AUSSCHN) > 1 THEN BEGIN
  497.       AUFWAERTS;
  498.       SPALTE := WWID;
  499.     END;
  500. {$ENDIF ELSEIF SPDISP}
  501.   END;
  502. END; { LINKS }
  503.  
  504. PROCEDURE CURSHOME;
  505. BEGIN
  506.   ZEILE := 1;
  507.   SPALTE := 0;
  508.   IF AUSSCHN > 0 THEN BEGIN
  509.     AUSSCHN := 0;
  510.     BILDAUFBAU;
  511.   END;
  512. END; { CURSHOME }
  513.  
  514. PROCEDURE CURSEND;
  515. BEGIN
  516.   IF AUSSCHN < MAXAUS THEN BEGIN
  517.     AUSSCHN := MAXAUS;
  518.     BILDAUFBAU;
  519.   END;
  520. {$IFDEF SPDISP}
  521.   ZEILE := 1;
  522.   SPALTE := WWID;
  523.   WHILE POINTERLIST[SPALTE,ZEILE] = NIL DO DEC(SPALTE);
  524.   ZEILE := WHIG;
  525.   WHILE POINTERLIST[SPALTE,ZEILE] = NIL DO DEC(ZEILE);
  526. {$ELSE}
  527.   ZEILE := WHIG;
  528.   SPALTE := 0;
  529.   WHILE POINTERLIST[SPALTE,ZEILE] = NIL DO DEC(ZEILE);
  530.   SPALTE := WWID;
  531.   WHILE POINTERLIST[SPALTE,ZEILE] = NIL DO DEC(SPALTE);
  532. {$ENDIF ELSEIF SPDISP}
  533. END; { CURSEND }
  534.  
  535. PROCEDURE SETCURSOR(PO:WORD);
  536. BEGIN
  537. {$IFDEF SPDISP}
  538.   SPALTE :=      PO DIV WHIG ;
  539.   ZEILE  := SUCC(PO MOD WHIG);
  540.   WHILE SPALTE > WWID DO BEGIN
  541.     DEC(SPALTE);
  542.     INC(AUSSCHN);
  543.   END;
  544. {$ELSE}
  545.   ZEILE := SUCC(PO DIV SUCC(WWID));
  546.   SPALTE := PO MOD SUCC(WWID);
  547.   WHILE ZEILE >= WHIG DO BEGIN
  548.     DEC(ZEILE);
  549.     INC(AUSSCHN);
  550.   END;
  551. {$ENDIF ELSEIF SPDISP}
  552. END; { SETCURSOR }
  553.  
  554. FUNCTION SUCHE:BOOLEAN;
  555. VAR   P,FP  : DIRPTR;
  556. BEGIN
  557.   PO := 0;
  558.   P  := START;
  559.   WHILE P^.NEXT <> NIL DO BEGIN
  560. (* search for filename stored in SR *)
  561.     IF P^.NAME < SR THEN BEGIN
  562.       INC(PO);
  563.       FP := P^.NEXT;
  564.     END;
  565.     P := P^.NEXT;
  566.   END; { WHILE }
  567.   SUCHE := ( COPY(FP^.NAME,1,LENGTH(SR)) = SR );
  568.  
  569.   ZEILE := SUCC(PO DIV SUCC(WWID));
  570.  
  571.   AUSSCHN := 0;
  572.   SETCURSOR(PO);
  573.   BILDAUFBAU;
  574. END; { SUCHE }
  575.  
  576. PROCEDURE ZEIGESR;
  577. VAR   TA  : BYTE;
  578. BEGIN
  579. {3.12.94}
  580.   IF (LO(WINDMAX)-LO(WINDMIN)) <= 20 THEN EXIT;
  581.   TA := TEXTATTR;
  582.   TEXTATTR := TARAND;
  583.   WINDOW(LO(WOM) + 2,HI(WOM)+2,LO(WUM),HI(WUM)+1);
  584.   GOTOXY(2,SUCC(HI(WINDMAX)-HI(WINDMIN)));
  585.   IF SR = '' THEN WRITE('════════════════════')
  586.              ELSE WRITE(' '+SR+' ═');
  587.   WINDOW(LO(WOM) + 2,HI(WOM)+3,LO(WUM),HI(WUM));
  588.   TEXTATTR := TA;
  589. END; { ZEIGESR }
  590.  
  591. PROCEDURE ALLTAGS(WAS:BOOLEAN);
  592. VAR   P  : DIRPTR;
  593. BEGIN
  594.   NTAGS := 0;
  595.   P := START;
  596.   REPEAT
  597.     IF (P^.ATTR AND (VOLUMEID OR DIRECTORY)) = 0 THEN BEGIN
  598.       P^.TAG := WAS;
  599.       IF WAS THEN INC(NTAGS);
  600.     END;
  601.     P := P^.NEXT;
  602.   UNTIL P = NIL;
  603.   BILDAUFBAU;
  604. END; { ALLTAGS }
  605.  
  606. BEGIN { SELECTDIRREC }
  607.   EXITKEY := 0;
  608.   SELECTDIRREC := NIL;
  609.   IF START = NIL THEN EXIT;
  610.   SR := '';
  611.   WINDOW(LO(WOM) + 2,HI(WOM)+3,LO(WUM),HI(WUM));
  612.  
  613. CALCULATE_WINDOW:
  614. {3.12.94}
  615.   GETANZWID;
  616.   IF ANZWID >= (LO(WINDMAX) - LO(WINDMIN)) THEN BEGIN
  617.     INC(DIRDISPLAYMODE);
  618.     IF DIRDISPLAYMODE > 4 THEN DIRDISPLAYMODE := 1;
  619.     GOTO CALCULATE_WINDOW;
  620.   END;
  621.   ZEILE := 1; SPALTE := 0; AUSSCHN := 0;
  622.  
  623. {3.12.94}
  624.   WWID := PRED( PRED(LO(WINDMAX) - LO(WINDMIN) ) DIV ANZWID);
  625.   PO := 0;
  626.   P := START; ANZAHL := 1;
  627.   WHILE P^.NEXT <> NIL DO BEGIN
  628. (* search for filename stored in SEARCHFOR *)
  629.     IF P^.NAME <= SEARCHFOR THEN PO := PRED(ANZAHL);
  630.     INC(ANZAHL);
  631.     P := P^.NEXT;
  632.   END; { WHILE }
  633.   IF P^.NAME <= SEARCHFOR THEN PO := PRED(ANZAHL);
  634.  
  635.   SETCURSOR(PO);
  636.  
  637.   ANZAHL := ANZAHL - (SUCC(WWID) * WHIG);
  638.   IF ANZAHL < 1 THEN MAXAUS := 0 ELSE BEGIN
  639. {$IFDEF SPDISP}
  640.     MAXAUS := ANZAHL DIV WHIG;
  641.     IF ANZAHL MOD WHIG > 0 THEN INC(MAXAUS);
  642. {$ELSE}
  643.     MAXAUS := ANZAHL DIV SUCC(WWID);
  644.     IF ANZAHL MOD SUCC(WWID) > 0 THEN INC(MAXAUS);
  645. {$ENDIF ELSEIF SPDISP}
  646.   END;
  647.  
  648.   BILDAUFBAU;
  649.   ENDE := FALSE;
  650.  
  651.   DX := 0;
  652.   DY := 0;
  653.   NTAGS := 0;
  654.   REPEAT
  655.     TEXTATTR := TASELECT;
  656.     IF ZEILE = 0 THEN INC(ZEILE); { 3.12.94 WARUM DENN NUR ???? }
  657.     GOTOXY(2+SPALTE*ANZWID,ZEILE);
  658.     ZEIGNAME(POINTERLIST[SPALTE,ZEILE]);
  659. {$IFDEF USEMOUSE}
  660.     REPEAT
  661.       GETMICKEYCOUNT(DXA,DYA);
  662.       DX := DX + DXA;
  663.       DY := DY + DYA;
  664.       IF ABS(DY) > 6 THEN BEGIN
  665.         IF DY < 0 THEN BEGIN
  666.           STUFFKEY(72 SHL 8);
  667.         END ELSE BEGIN
  668.           STUFFKEY(80 SHL 8);
  669.         END;
  670.         DY := 0;
  671.       END;
  672.       IF ABS(DX) > 32 THEN BEGIN
  673.         IF DX < 0 THEN BEGIN
  674.           STUFFKEY(75 SHL 8);
  675.         END ELSE BEGIN
  676.           STUFFKEY(77 SHL 8);
  677.         END;
  678.         DX := 0;
  679.       END;
  680.     UNTIL KEYPRESSED OR MOUSEPRESSED;
  681.     MKB := READKEYORBUTTON;
  682.     IF LO(MKB) = $E0 THEN BEGIN
  683. { delete 'E0' for normal keyboard driver }
  684.       MKB := MKB AND $FF00;
  685.     END;
  686.  
  687.     IF MKB = MOUSELFT THEN MKB := 13; { left mousekey = <Ret> }
  688.     IF MKB = MOUSERT  THEN MKB := 27; { right mousekey = <Esc> }
  689. {$ELSE}
  690.     MKB := READKEYWORD;
  691. {$ENDIF USEMOUSE}
  692.     FOR I := 1 TO 8 DO IF MKB = EXITKEYS[I] THEN BEGIN
  693.       EXITKEY := I;
  694.       MKB := 13{27};
  695.     END;
  696.     CASE CH1 OF
  697.        ^I : BEGIN
  698.               INC(DIRDISPLAYMODE);
  699.               IF DIRDISPLAYMODE > 4 THEN DIRDISPLAYMODE := 1;
  700.               GOTO CALCULATE_WINDOW;
  701.             END;
  702.        ^[ : BEGIN { ESC }
  703.               SELECTDIRREC := NIL;
  704.               ENDE := TRUE;
  705.             END;
  706.        ^T : ALLTAGS(TRUE);
  707.        ^U : ALLTAGS(FALSE);
  708.        ^M : BEGIN { ENTER }
  709.               SELECTDIRREC := POINTERLIST[SPALTE,ZEILE];
  710.               ENDE := TRUE;
  711.             END;
  712.        #8 : BEGIN
  713.               SR := '';
  714.               ZEIGESR;
  715.             END;
  716.       ' ' : WITH POINTERLIST[SPALTE,ZEILE]^ DO BEGIN
  717.               IF (ATTR AND (VOLUMEID OR DIRECTORY)) = 0 THEN BEGIN
  718.                 TAG := NOT TAG;
  719.                 IF TAG THEN INC(NTAGS)
  720.                        ELSE DEC(NTAGS);
  721.                 STUFFKEY(77 SHL 8);
  722.               END;
  723.               SR := '';
  724.               ZEIGESR;
  725.             END;
  726.   #1..#31 : BEGIN END;
  727.        #0 : BEGIN { function keys }
  728.               IF (CH2 <> #73) AND (CH2 <> #81) THEN BEGIN
  729.                 GOTOXY(2+SPALTE*ANZWID,ZEILE);
  730.                 TEXTATTR := TANONSEL;
  731.                 ZEIGNAME(POINTERLIST[SPALTE,ZEILE]);
  732.               END;
  733.             END;
  734.     ELSE
  735.  
  736.       SR := SR + UPCASE(CH1);
  737.       IF NOT SUCHE THEN SR := '';
  738.       ZEIGESR;
  739.     END; { CASE CH1 }
  740.     CASE CH2 OF
  741.       #72 : BEGIN { UP }
  742.               SR := '';
  743.               AUFWAERTS;
  744.               ZEIGESR;
  745.             END;
  746.       #80 : BEGIN { DOWN }
  747.               SR := '';
  748.               ABWAERTS;
  749.               ZEIGESR;
  750.             END;
  751.       #75 : BEGIN { LEFT }
  752.               SR := '';
  753.               LINKS;
  754.               ZEIGESR;
  755.             END;
  756.       #77 : BEGIN { RIGHT }
  757.               SR := '';
  758.               RECHTS;
  759.               ZEIGESR;
  760.             END;
  761.       #73 : BEGIN { PG UP }
  762.               SR := '';
  763.               IF AUSSCHN > 0 THEN BEGIN
  764. {$IFDEF SPDISP}
  765.                 IF AUSSCHN > PRED(WWID) THEN DEC(AUSSCHN,WWID)
  766.                                         ELSE AUSSCHN := 0;
  767. {$ELSE}
  768.                 IF AUSSCHN > PRED(WHIG) THEN DEC(AUSSCHN,PRED(WHIG))
  769.                                         ELSE AUSSCHN := 0;
  770. {$ENDIF ELSEIF SPDISP}
  771.               END ELSE CURSHOME;
  772.               BILDAUFBAU;
  773.               ZEIGESR;
  774.             END;
  775.       #81 : BEGIN { PG DOWN }
  776.               SR := '';
  777.               IF AUSSCHN < MAXAUS THEN BEGIN
  778. {$IFDEF SPDISP}
  779.                 INC(AUSSCHN,WWID);
  780.                 IF AUSSCHN > MAXAUS THEN AUSSCHN := MAXAUS;
  781.                 WHILE POINTERLIST[SPALTE,ZEILE] = NIL DO DEC(ZEILE);
  782. {$ELSE}
  783.                 INC(AUSSCHN,PRED(WHIG));
  784.                 IF AUSSCHN > MAXAUS THEN AUSSCHN := MAXAUS;
  785.                 WHILE POINTERLIST[SPALTE,ZEILE] = NIL DO DEC(SPALTE);
  786. {$ENDIF ELSEIF SPDISP}
  787.               END ELSE CURSEND;
  788.               BILDAUFBAU;
  789.               ZEIGESR;
  790.             END;
  791.       #71 : BEGIN { HOME }
  792.               SR := '';
  793.               CURSHOME;
  794.               ZEIGESR;
  795.             END;
  796.       #79 : BEGIN { END }
  797.               SR := '';
  798.               CURSEND;
  799.               ZEIGESR;
  800.             END;
  801.     END; { CASE CH2 }
  802.   UNTIL ENDE;
  803.  
  804.   IF NTAGS > 0 THEN BEGIN
  805.     P := START;
  806.     REPEAT
  807. {$V-}
  808.       IF P^.TAG THEN PRINTNAME(AKTPATH+P^.NAME);
  809. {$V+}
  810.       P := P^.NEXT;
  811.     UNTIL P = NIL;
  812.   END;
  813.  
  814.   WINDOW(LO(WOM) + 2,HI(WOM)+2,LO(WUM),HI(WUM));
  815. END; { SELECTDIRREC }
  816.  
  817.  
  818. PROCEDURE SAVEWINDOW;
  819. VAR   I  : INTEGER;
  820.  
  821. PROCEDURE LINIE;
  822. VAR   WID : BYTE;
  823. BEGIN
  824.   WID := PRED(LO(WINDMAX) - LO(WINDMIN));
  825.   PUTCHARATTR('═',TEXTATTR,WID);
  826.   GOTOXY(WHEREX+WID,WHEREY);
  827. END;
  828.  
  829. BEGIN
  830.   WHIG := PRED( (HI(WINDMAX) - HI(WINDMIN) - 1) );
  831.   WOM  := WINDMIN;
  832.   WUM  := WINDMAX;
  833.   TAALT := TEXTATTR;
  834.   XPOS := WHEREX;
  835.   YPOS := WHEREY;
  836.   PUSHWINDOW;
  837.  
  838.   TEXTATTR := TARAND;
  839.   GOTOXY(1,1);
  840.   WRITE('╔');
  841.   LINIE;
  842.   WRITE('╗');
  843.   FOR I := 2 TO (HI(WINDMAX) - HI(WINDMIN)) DO BEGIN
  844.     GOTOXY(1,I); WRITE('║');
  845.     GOTOXY(SUCC(LO(WINDMAX)-LO(WINDMIN)),I); WRITE('║');
  846.   END;
  847.   WRITE('╚');
  848.   LINIE;
  849.   PUTCHARATTR('╝',TEXTATTR,1);
  850.  
  851.   WINDOW(LO(WOM)+2,HI(WOM)+2,LO(WUM),HI(WUM));
  852. END; { SAVEWINDOW }
  853.  
  854.  
  855. PROCEDURE RESTOREWINDOW;
  856. BEGIN
  857.   POPWINDOW;
  858.   WINDOW(SUCC(LO(WOM)),SUCC(HI(WOM)),SUCC(LO(WUM)),SUCC(HI(WUM)));
  859.  
  860.   GOTOXY(XPOS,YPOS);
  861.   TEXTATTR := TAALT;
  862. END; { RESTOREWINDOW }
  863.  
  864.  
  865. FUNCTION  SELECTFILE(PTH,NAME:STRING):STRING;
  866. VAR   EXECOM,FILEPTR  : DIRPTR;
  867.       SP,I,WINDW      : BYTE;
  868.       NFILES,NDIRS    : WORD;
  869.       PATH,PM         : STRING;
  870.       S1              : STRING[80];
  871.       NS              : STRING[10];
  872.       DIRECTORY       : BOOLEAN;
  873.       SR              : SEARCHREC;
  874. LABEL ENDE;
  875.  
  876. BEGIN { SELECTFILE }
  877.   SELECTFILE := '';
  878. {3.12.94}
  879.   GETANZWID;
  880.   WHILE (ANZWID+3) > (LO(WINDMAX) - LO(WINDMIN)) DO BEGIN
  881.     IF LO(WINDMAX) < 78 THEN BEGIN
  882.       INC(WINDMAX);
  883.     END ELSE BEGIN
  884.       IF LO(WINDMIN) > 1 THEN DEC(WINDMIN);
  885.     END;
  886.   END;
  887.   WHILE (HI(WINDMAX) - HI(WINDMIN)) < 3 DO BEGIN
  888.     IF HI(WINDMAX) < 25 THEN BEGIN
  889.       INC(WINDMAX,$100);
  890.     END ELSE BEGIN
  891.       IF HI(WINDMIN) > 1 THEN DEC(WINDMIN,$100);
  892.     END;
  893.   END;
  894.  
  895.   SAVEWINDOW;
  896.  
  897.   EXECOM := NIL;
  898.   IF PTH = '' THEN GETDIR(0,PATH) ELSE PATH := PTH;
  899.   REPEAT
  900.     IF PATH[LENGTH(PATH)] <> '\' THEN PATH := PATH + '\';
  901.     FREEDIR(EXECOM);
  902.     TEXTATTR := TANONSEL;
  903.     CLRSCR;
  904.     TEXTATTR := $4E;
  905.     WRITE(' warten ');
  906.     READDIR(PATH+NAME,NFILES,NDIRS,EXECOM);
  907.  
  908.     HIDECURSOR;
  909.     STR(NFILES,NS);
  910.     AKTPATH := PATH;
  911.     WINDW := LO(WINDMAX) - LO(WINDMIN) - 2;
  912.     IF (POS('.*',NAME) > 0) AND (INCLUDE[1] <> '') THEN BEGIN
  913.       S1 := ' '+PATH+'*';
  914.       I := 1;
  915.       WHILE (I <= ANZINCLUDE) AND ( (LENGTH(S1)+5) < WINDW ) DO BEGIN
  916.         IF (I > 1) AND (INCLUDE[I] <> '') THEN S1 := S1 + ',';
  917.         S1 := S1 + INCLUDE[I];
  918.         INC(I);
  919.       END;
  920.       IF I <= ANZINCLUDE THEN S1 := S1+'..';
  921.     END ELSE BEGIN
  922.       S1 := ' '+PATH+NAME;
  923.     END;
  924. { 18.12.94 }
  925.     IF LENGTH(S1) > WINDW THEN BEGIN
  926.       SP := LENGTH(S1);
  927.       WHILE (SP > 0) AND (S1[SP] <> '\') DO DEC(SP);
  928.       IF SP > 1 THEN DEC(SP);
  929.       WHILE (SP > 0) AND (S1[SP] <> '\') DO DEC(SP);
  930.       IF SP > 4 THEN BEGIN
  931.         DELETE(S1,4,SP-4);
  932.         INSERT('..',S1,4);
  933.       END;
  934.     END;
  935.     IF (LENGTH(S1)+LENGTH(NS)+7) < WINDW THEN S1 := S1 + +' '+NS+' Files ';
  936. { 3.12.94 }
  937.     IF LENGTH(S1) > WINDW THEN S1 := NAME;
  938.  
  939.     TEXTATTR := TANONSEL; GOTOXY(1,1); CLREOL;
  940.     GOTOXY((LO(WINDMAX)-LO(WINDMIN)-LENGTH(S1)+2) SHR 1,1);
  941.     TEXTATTR := TATITEL;  WRITE(S1);
  942.  
  943.     FILEPTR := SELECTDIRREC(EXECOM,NFILES+NDIRS);
  944.     NORMCURSOR;
  945.     PM := PATH;
  946.  
  947.     IF FILEPTR = NIL THEN BEGIN
  948.       IF (NFILES + NDIRS) = 0 THEN BEGIN
  949.         TEXTATTR := TANONSEL;
  950.         WRITELN(#7);
  951.         CASE DOSERROR OF
  952. (*
  953.            3 : WRITELN(' Pfad nicht gefunden');
  954.           18 : WRITELN(' keine Dateien gefunden');
  955.         ELSE
  956.           WRITELN('ungültiges Laufwerk');
  957.         END;
  958.         WRITELN(' Taste drücken');
  959. *)
  960.            3 : WRITELN(' Path not found');
  961.           18 : WRITELN(' no files found');
  962.         ELSE
  963.           WRITELN('not a valid drive');
  964.         END;
  965.         WRITELN(' press any key');
  966. {$IFDEF USEMOUSE}
  967.         IF READKEYORBUTTON = 0 THEN;
  968. {$ELSE USEMOUSE}
  969.         IF READKEYWORD = 0 THEN;
  970. {$ENDIF USEMOUSE}
  971.       END;
  972. { <ESC> = cancel }
  973.       GOTO ENDE;
  974.     END;
  975.  
  976.     IF EXITKEY = 0 THEN BEGIN
  977.       DIRECTORY := (FILEPTR^.ATTR AND DOS.DIRECTORY) <> 0;
  978. { NAME[1] = DRIVEMARK is a name of a drive }
  979.       IF FILEPTR^.NAME[1] = DRIVEMARK THEN BEGIN
  980.         PATH := COPY(FILEPTR^.NAME,2,PRED(LENGTH(FILEPTR^.NAME))) + '\';
  981.         FINDFIRST(PATH+'*.*',ANYFILE,SR);
  982.         IF NOT (DOSERROR IN [0,18]) THEN BEGIN
  983.           WRITE(#7);
  984.           PATH := PM;
  985.         END;
  986.       END ELSE BEGIN
  987.  
  988. { DIRECTORIES are marked as NAME[1] = DIRMARK }
  989.         IF (FILEPTR^.NAME[1] = DIRMARK) OR
  990.            (FILEPTR^.NAME = ' ..')
  991.         THEN BEGIN
  992.           DELETE(FILEPTR^.NAME,1,1);
  993.           IF (LENGTH(FILEPTR^.NAME) > 8) AND
  994.              (POS('.',FILEPTR^.NAME) = 0) THEN INSERT('.',FILEPTR^.NAME,9);
  995.         END;
  996.         PATH := PATH + FILEPTR^.NAME;
  997.  
  998.         IF (FILEPTR^.NAME = '..') THEN BEGIN
  999.           SP := LENGTH(PATH) - 3;
  1000.           PATH := COPY(PATH,1,SP);
  1001.           WHILE PATH[SP] <> '\' DO DEC(SP);
  1002.           PATH := COPY(PATH,1,PRED(SP));
  1003.         END;
  1004.       END;
  1005.     END ELSE BEGIN
  1006.       SEARCHFOR := FILEPTR^.NAME;
  1007.       IF (FILEPTR^.NAME[1] = DIRMARK) OR (FILEPTR^.NAME[1] = DRIVEMARK) THEN BEGIN
  1008.         SELECTFILE := PATH;
  1009.       END ELSE BEGIN
  1010.         SELECTFILE := PATH + FILEPTR^.NAME;
  1011.       END;
  1012.       GOTO ENDE;
  1013.     END; { IF EXITKEY = 0 }
  1014.   UNTIL (NOT DIRECTORY) OR (EXITKEY <> 0);
  1015.   SEARCHFOR := FILEPTR^.NAME;
  1016.   SELECTFILE := PATH;
  1017.  
  1018. ENDE:
  1019.   RESTOREWINDOW;
  1020.   FREEDIR(EXECOM);
  1021. END; { SELECTFILE }
  1022.  
  1023.  
  1024. PROCEDURE DUMMY(S:STRING);
  1025. BEGIN
  1026. END; { DUMMY }
  1027.  
  1028.  
  1029. BEGIN
  1030.   PRINTNAME := DUMMY;
  1031.   AllDrives := LogiCalDrives;
  1032. END.
  1033.  
  1034.